﻿namespace NetFx.SMIL.References
{
  using System;
  using System.Text;
  using System.Collections;
  using System.Collections.Generic;

  using System.Reflection;
  using System.Reflection.Emit;
  using System.Runtime.InteropServices;

  using System.Diagnostics;
  using System.Diagnostics.CodeAnalysis;
  using System.Diagnostics.SymbolStore;
  using System.Security;
  using System.Security.Permissions;

  using NetFx.MSIL;

  /// <summary>
  /// 对常数的引用（常数封装）。
  /// </summary>
  /// <remarks>
  /// 仅支持 ValueType 和 String。
  /// 对于非Primitive类型的ValueType将指出异常。
  /// </remarks>
  public class ConstRef:Reference
  {
    #region Statics
    public static ConstRef of(ValueType constValue)
    {
      return new ConstRef(constValue);
    }
    public static ConstRef of(string constValue)
    {
      return new ConstRef(constValue);
    }
    #endregion
    #region Properties
    public virtual object ReflectInfo
    {
      get
      {
        return this.referenced;
      }
    }
    public virtual bool HasReflectInfo
    {
      get
      {
        return this.ReflectInfo != null;
      }
    }

    public virtual string StringValue
    {
      get
      {
        return this.Referenced as string;
      }
    }
    public virtual ValueType NumericValue
    {
      get
      {
        return this.referenced is ValueType ?
          (ValueType)this.referenced :
          0;
      }
    }
    public virtual bool IsValueType
    {
      get
      {
        return this.referenced is ValueType;
      }
    }
    public virtual bool IsString
    {
      get
      {
        return this.referenced is string;
      }
    }
    #endregion
    #region Constructors
    public ConstRef(ValueType constValue) : base(constValue) 
    {
      if (constValue != null)
      {
        if (!constValue.GetType().IsPrimitive)
          throw new ArgumentException("constValue should be PrimitiveType");
      }
    }
    public ConstRef(string constValue) : base(constValue) { }
    #endregion
    #region Methods
    public override string ToString()
    {
      return this.IsString ?
        string.Format("\"{0}\"", this.StringValue) :
        string.Format("{0}", this.NumericValue);
    }
    #endregion
  }
}
